﻿using System;
using System.Collections.Generic;
using System.Text;
using System.Net;
using System.Net.Sockets;
using System.IO;
using System.Threading;
using System.Windows.Threading;

namespace Chaos.network
{
    public class tcpconnection : connection
    {
        TcpClient m_tcpclient;

        public TcpClient TcpClient
        {
            get { return m_tcpclient; }
        }

        public tcpconnection(TcpClient in_tcpClient, IPEndPoint in_IPEndPoint)
        {
            m_tcpclient = in_tcpClient;
        }

        public override void start()
        {
            m_thread = new Thread(new ThreadStart(threadmain));
            m_thread.Name = "tcpconnection";
            m_thread.Priority = ThreadPriority.BelowNormal;
            m_thread.Start();
            base.start();
        }

        public override void abort()
        {
            if (m_tcpclient != null)
            {
                if (m_tcpclient.Connected)
                {
                    m_tcpclient.Close();
                    //m_thread.Abort();
                    m_thread.Join();
                    base.abort();
                }
            }
        }

        void threadmain()
        {
            byte[] receiveBuffer = new byte[1024 * 1024];
            connection.estate state = connection.estate.kState_ReadHeader;
            int bytesToRead = 4;
            int bytesRead = 0;

            while (m_tcpclient.Connected)
            {
                try
                {
                    if (m_tcpclient.GetStream().DataAvailable)
                    {
                        if (state == estate.kState_ReadHeader)
                        {
                            bytesRead = m_tcpclient.GetStream().Read(receiveBuffer, bytesRead, bytesToRead);
                            if (bytesRead == 4)
                            {
                                bytesToRead = BitConverter.ToInt32(receiveBuffer, 0) - 4;
                                bytesRead = 0;
                                state = estate.kState_ReadPacket;
                            }
                        }
                        else
                        {
                            bytesRead = m_tcpclient.GetStream().Read(receiveBuffer, bytesRead, bytesToRead - bytesRead);
                            if (bytesRead == bytesToRead)
                            {
                                byte[] buffer = new byte[bytesRead];
                                Array.Copy(receiveBuffer, 0, buffer, 0, bytesToRead);
                                recievedata(m_ipendpoint, buffer, bytesToRead);                                
                              
                                state = estate.kState_ReadHeader;
                                bytesRead = 0;
                                bytesToRead = 4;
                            }
                        }
                    }
                    else
                    {
                        Thread.Sleep(100);
                    }
                }
                catch (SocketException e)
                {
                    Thread.Sleep(100);
                    System.Diagnostics.Debug.WriteLine(e.ToString());
                }
                catch (Exception e)
                {
                    System.Diagnostics.Debug.WriteLine(e.ToString());
                }
            }

            try
            {
                m_tcpclient.Close();
            }
            catch (System.Exception e)
            {
                System.Diagnostics.Debug.WriteLine(e.ToString());
            }

            m_tcpclient = null;
        }

        public override void senddata(IPEndPoint to, byte[] buffer, int bufflen)
        {
            try
            {
                m_tcpclient.GetStream().Write(buffer, 0, bufflen);
            }
            catch (Exception e)
            {
                System.Diagnostics.Debug.WriteLine(e.ToString());
            }

        }        
    }
}
